{
 "cells": [
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "# The Robot World\n",
    "\n",
    "A robot, much like you, perceives the world through its \"senses.\" For example, self-driving cars use video, radar, and Lidar, to observe the world around them. As cars gather data, they build up a 3D world of observations that tells the car where it is, where other objects (like trees, pedestrians, and other vehicles) are, and where it should be going! \n",
    "\n",
    "In this section, we'll be working with a 2D representation of the world for simplicity, and because two dimensions are often all you'll need to solve a certain problem.\n",
    "\n",
    "<img src=\"image/lidar.png\" width=\"50%\" height=\"50%\">"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "### 2D Arrays \n",
    "\n",
    "This demonstration shows how to represent a robot's world as a 2D array of observations, in this case, we'll work with a simple example that uses  integer variables to represent whether there is (1) or is not (0) a tree present at that location on the grid.\n",
    "\n",
    "For example, a robot that sees a 2x4 world may see this 2D array:\n",
    "\n",
    "```python\n",
    "[[0, 0, 0, 1],\n",
    " [1, 0, 0, 0]]\n",
    "```\n",
    "\n",
    "Which indicates that there are only two trees: one at the top rightmost point in its world, and one at the leftmost bottom. In fact the coordinates or indices of these tree locations are [0, 3] for the top-right corner and [1, 0] for the bottom-left. This has to do with the way indices are counted in Python. A graphical representation is shown below.\n",
    "\n",
    "<img src=\"image/2D_trees.png\" width=\"50%\" height=\"50%\">"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "Note that in this demonstration, we'll be using the `numpy` library again, which is a Python library that helps us create and manipulate arrays.\n",
    "\n",
    "### Define the 2D world"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 2,
   "metadata": {},
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "[[0 0 0 1 0]\n",
      " [0 0 0 1 0]\n",
      " [0 1 1 0 0]\n",
      " [0 0 0 0 1]\n",
      " [1 0 0 1 0]\n",
      " [1 0 0 0 0]]\n"
     ]
    }
   ],
   "source": [
    "import numpy as np\n",
    "\n",
    "# A simple robot world can be defined by a 2D array\n",
    "# Here is a 6x5 (num_rows x num_cols) world\n",
    "world = np.array([ [0, 0, 0, 1, 0],\n",
    "                   [0, 0, 0, 1, 0],\n",
    "                   [0, 1, 1, 0, 0],\n",
    "                   [0, 0, 0, 0, 1],\n",
    "                   [1, 0, 0, 1, 0],\n",
    "                   [1, 0, 0, 0, 0] ])\n",
    "\n",
    "# Visualize the world\n",
    "print(world)"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 3,
   "metadata": {},
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "The shape of this array is: (6L, 5L)\n",
      "Notice that the x and y dimensions are in the opposite order than usual!\n",
      "It's height is: 5, and it's length/width is: 6\n"
     ]
    }
   ],
   "source": [
    "# Print out some information about the world\n",
    "\n",
    "print('The shape of this array is: ' + str(world.shape))\n",
    "print('Notice that the x and y dimensions are in the opposite order than usual!')\n",
    "print('It\\'s height is: ' + str(world.shape[1]) + \n",
    "      ', and it\\'s length/width is: ' + str(world.shape[0]))"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "### Read and compare values in a 2D array"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 4,
   "metadata": {},
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "\n",
      "\n",
      "Value at index [3, 0] = 0\n",
      "\n",
      "The first three values in row 2 : 0, 1, 1\n",
      "\n",
      "Do the first two values match? True\n"
     ]
    }
   ],
   "source": [
    "# Access a location and read its value\n",
    "value = world[3][0]\n",
    "print('\\n')\n",
    "print('Value at index [3, 0] = ' +str(value))\n",
    "\n",
    "# Read the first three items in the 3rd row\n",
    "row = 2\n",
    "column_index = 0\n",
    "value_left = world[row, column_index]\n",
    "value_middle = world[row, column_index + 1]\n",
    "value_right = world[row, column_index + 2]\n",
    "\n",
    "print('\\nThe first three values in row 2 : ' +str(value_left)+', '\n",
    "                                              +str(value_middle) +', '\n",
    "                                              +str(value_right) )\n",
    "\n",
    "# Compare the first two values and print the result\n",
    "compare = world[0][0] == world[0][1]\n",
    "print('\\nDo the first two values match? ' + str(compare))"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "### Change an Array and Plant a Tree!"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 5,
   "metadata": {},
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "\n",
      "[[0 0 1 1 0]\n",
      " [0 0 0 1 0]\n",
      " [0 1 1 0 0]\n",
      " [0 0 0 0 1]\n",
      " [1 0 0 1 0]\n",
      " [1 0 0 0 0]]\n"
     ]
    }
   ],
   "source": [
    "# Define a function to plant a tree \n",
    "# and change the value of the array in that location\n",
    "def plant_tree(y, x):\n",
    "    # check that the indices are in the boundaries of the array dimensions\n",
    "    if(y < world.shape[0] and x < world.shape[1]):\n",
    "        world[y,x] = 1\n",
    "        print('\\n' + str(world)) # prints a newline and the current world\n",
    "\n",
    "# Call the function at the location x = 3, and y = 2\n",
    "# You can call this multiple times in a row\n",
    "plant_tree(0, 2)"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {
    "collapsed": true
   },
   "outputs": [],
   "source": []
  }
 ],
 "metadata": {
  "anaconda-cloud": {},
  "kernelspec": {
   "display_name": "Python 2",
   "language": "python",
   "name": "python2"
  },
  "language_info": {
   "codemirror_mode": {
    "name": "ipython",
    "version": 2
   },
   "file_extension": ".py",
   "mimetype": "text/x-python",
   "name": "python",
   "nbconvert_exporter": "python",
   "pygments_lexer": "ipython2",
   "version": "2.7.16"
  }
 },
 "nbformat": 4,
 "nbformat_minor": 1
}
